#coding=utf-8

require "aio/core"
require "rexml/document"

=begin
<CompareModule description='这个模块输出为XML文件，用于和基准值比较' author='Elin'>
  <device device_name='COS_1'>
    <cpu cmd='display cpu-usage'>
      <slot_id val='1'>
      <seonds_5 val='9%'>
      <minute_1 val='9%'>
      <minutes_5 val='9%'>
    </cpu>
    ...
  </device>
  ...
</CompareModule>
=end

class Aio::Module::OutputStyle::CompareXML < Aio::Module::OutputStyle

  def initialize
    super({
      :author			=> "Elin",
      :description => "这个模块输出为XML文件，用于和基准值比较。",
      :file_suffix => "xml",
    })
  end

  def generate
    file = File.new(output_file, "w+")
    doc = REXML::Document.new
    root = doc.add_element("CompareModule",{ 
      'description' => self.output_info[:description], 
      'author' => self.output_info[:author]}
                          )
    # 第一层， device 节
    each_devices_with_useful do |device_name, useful|
      device_root = root.add_element('device', {'device_name' => device_name})
      useful.each_pair do |cmd_name, info|
        info.each_pair do |c, i|
          cmd_root = device_root.add_element(c.to_s, {'cmd' => cmd_name})
          if i.class == Hash
            loop_element(device_root, cmd_root, i)
          elsif i.kind_of? String
            cmd_root.add_attribute('val', i)
          else
            # 这一段留作观察，很有可能没有作用
            puts "output/style/compare_xml.rb# add_element"
            cmd_root.add_element(c.to_s, {'val' => i.to_s})
          end
        end
      end
    end
    #doc.write(STDOUT, 2); puts
    doc.write(file, 2)
  end

  # 迭代方法
  def loop_element(parent, son, info)
    # 如果val为Hash，则继续循环
    info.each_pair do |key, val|
      if val.class == Hash
        grandson = son.add_element(safe(key))
        loop_element(son, grandson, val) 
      end
    end

    info.each_pair do |key, val|
      next if val.class == Hash
      son.add_element(safe(key), {'val' => val.to_s})
    end
  end

  # 将可能的字符串问题转化为特殊安全字符，再在解析时恢复
  # 恢复地方是 input/style/compare_xml# convert
  # 	1.接口中的 / 字符转化为两个下划线 __
  #   2.路由表中以数字开头的在字符串前面加上 _i
  def safe(key)
    begin
    key = key.to_s
    key.gsub!('/', '__') if /\//.match(key) 
    key.gsub!(' ', '_sp_') if /\s/.match(key)
    key.insert(0, "_i") if /^\d+/.match(key)
    key
    rescue
      key = key.dup
      retry
    end
  end
end
